/**
 * 推送打包结果至git
 * 
 */

const git = require('../git/index');

const { AsyncSeriesBailHook } = require('tapable');

const eventEmitter = require('../../common/eventbus');

const readline = require('../../common/inputListener');

const error = require('../../common/error');

const path = require('path');

/**
 * 
 * @param {*} msg readline 输入的消息
 * @param {*} resolve promise 的resolve
 * @param {*} reject promise reject
 * @param {*} reOperator 回调函数
 * @param {*} operatorName 操作名
 * @param {*} rl readline的实例
 */
function rlFun(msg, resolve, reject, reOperator, operatorName, cwd) {

  if (msg === 'quit') reject('用户输入quit，');

  if (msg === 'yes') {

    let { result } = reOperator(null,cwd);

    if (result) {

      resolve();

    } else {

      reject(operatorName + '操作失败，请检查，');

    }

  } else {

    console.log('请输入yes继续，quit退出程序');

  };

}

module.exports = async function (envData) {

  const { outputDir, platform, version, memo } = envData;

  const workDir = path.join(process.cwd(), outputDir);

  const pushPackHook = new AsyncSeriesBailHook();

  let rl;

  pushPackHook.tapPromise('checkGit',()=>{

    return new Promise((resolve, reject) => {

      if(!git.check(workDir).result) {
        
        reject('当前环境下git不可用，请检查git环境。确保您已安装git 并且已登录。');

        return

      };

      if(!git.checkStatus(workDir).result) {
        
        reject(`目录:${workDir} git仓库不可用，请检查${workDir}目录下的 git 仓库。当前的检测指令为 git status。`);

        return

      };

      resolve();

    });

  });

  pushPackHook.tapPromise('pull', () => {

    return new Promise((resolve, reject) => {

      rl = readline.init();

      let { result } = git.pull(workDir);

      if (!result) {

        rl.on('line', input => {

          rlFun(input, resolve, reject, git.pull, 'git pull', workDir);

        });

        rl.question('git pull 失败是否重新拉取？输入yes重新执行，quit退出程序:', answer => {

          rlFun(answer, resolve, reject, git.pull, 'git pull', workDir);

        });

      } else {

        resolve();

      }

    });

  });

  pushPackHook.tapPromise('add', () => {

    return new Promise((resolve, reject) => {

      let { result } = git.add(workDir,workDir);

      if (!result) {

        reject('git add 操作失败，');

      } else {

        resolve();

      }

    });

  });
  
  pushPackHook.tapPromise('pushBefore',()=>{

    return new Promise((resolve,reject)=>{
            
      rl.close();

      rl = readline.init();

      rl.question('打包文件已提交至暂存区 是否自动推送？输入yes自动推送，其他任意输入将退出程序。', answer => {

        if(answer === 'yes'){

          resolve();

        } else {

          // 直接结束跳过后面的push指令
          resolve(true);

        }

      });

    });

  });

  pushPackHook.tapPromise('commit', () => {

    return new Promise((resolve, reject) => {

      let msg = `平台：${platform}版本${version}打包原由：${memo && memo.replace(/\u0020/g,'_')}`;

      let {result} = git.commit(msg,workDir);

      if(!result){

        reject('git commit 操作失败，');

      }else{

        resolve();

      }

    });

  });

  pushPackHook.tapPromise('push', () => {

    return new Promise((resolve, reject) => {
            
      rl.close();

      rl = readline.init();

      let { result } = git.push(null,workDir);

      if(!result){

        rl.on('line', input => {

          rlFun(input, resolve, reject, git.push, 'git pull', workDir);

        });

        rl.question('git push 失败是否重新推送？输入yes重新执行，quit退出程序:', answer => {

          rlFun(answer, resolve, reject, git.push, 'git pull', workDir);

        });

      }else{

        resolve();

      }

    });

  });


  function call() {

    return pushPackHook.promise();

  }

  await call().then(()=>{

    eventEmitter.emit('operator.pushPack.complete');

  }).catch(msg => {

    rl && rl.close();

    error(msg && msg + '程序退出');

  }).finally(()=>{

    rl.close();

  });

}